package org.mcjug.locationmailer.activity;

import org.mcjug.locationmailer.R;

import android.app.Dialog;
import android.content.Context;
import android.content.res.TypedArray;
import android.os.Bundle;
import android.preference.DialogPreference;
import android.text.SpannableString;
import android.text.Spanned;
import android.text.TextUtils;
import android.util.AttributeSet;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.ArrayAdapter;
import android.widget.ImageButton;
import android.widget.MultiAutoCompleteTextView;
import android.widget.Spinner;

public abstract class AbstractEmailPreference extends DialogPreference {
    private MultiAutoCompleteTextView editText;
    private String lastEditValue;
    private Spinner spinner;

    public AbstractEmailPreference(Context ctxt) {
        this(ctxt, null);
    }

    public AbstractEmailPreference(Context ctxt, AttributeSet attrs) {
        this(ctxt, attrs, 0);
    }

    public AbstractEmailPreference(Context ctxt, AttributeSet attrs, int defStyle) {
        super(ctxt, attrs, defStyle);
    }

    protected void showDialog(Bundle state) {
        super.showDialog(state);

        // getDialog() is null until after the call to super.showDialog(state);
        Dialog dialog = getDialog();

        // Set the value of the preference
        editText = (MultiAutoCompleteTextView) dialog.findViewById(R.id.emailPrefEdit);
        editText.setText(lastEditValue);
        editText.setAdapter(getKeywordData());
        editText.setTokenizer(new SpaceTokenizer());

        spinner = (Spinner) getDialog().findViewById(R.id.emailPrefSpinner);
        spinner.setAdapter(getKeywordData());

        final ImageButton button = (ImageButton) getDialog().findViewById(R.id.emailPrefInsertButton);
        button.setOnClickListener(new OnClickListener() {
            public void onClick(View v) {
                // Get the value from the spinner
                String text = spinner.getSelectedItem().toString();

                // Start maybe after end if user selected text backwards
                int start = editText.getSelectionStart();
                int end = editText.getSelectionEnd();

                // Insert the value from the spinner
                editText.getText().replace(Math.min(start, end), Math.max(start, end), text, 0, text.length());
            }
        });

    }

    protected void onDialogClosed(boolean positiveResult) {
        super.onDialogClosed(positiveResult);

        // If OK button was pressed then persist the change
        if (positiveResult) {
            lastEditValue = editText.getText().toString();
            if (callChangeListener(lastEditValue)) {
                persistString(lastEditValue);
            }
        }
    }

    // Return the default value
    protected Object onGetDefaultValue(TypedArray a, int index) {
        return (a.getString(index));
    }

    // Set the initial value to the persisted value if it exists, otherwise, use the default value
    protected void onSetInitialValue(boolean restoreValue, Object defaultValue) {
        lastEditValue = (restoreValue ? getPersistedString(lastEditValue) : (String) defaultValue);
    }

    protected abstract ArrayAdapter<String> getKeywordData();

    public class SpaceTokenizer implements MultiAutoCompleteTextView.Tokenizer {

        public int findTokenStart(CharSequence text, int cursor) {
            int i = cursor;

            while (i > 0 && text.charAt(i - 1) != ' ') {
                i--;
            }
            while (i < cursor && text.charAt(i) == ' ') {
                i++;
            }

            return i;
        }

        public int findTokenEnd(CharSequence text, int cursor) {
            int i = cursor;
            int len = text.length();

            while (i < len) {
                if (text.charAt(i) == ' ') {
                    return i;
                } else {
                    i++;
                }
            }

            return len;
        }

        public CharSequence terminateToken(CharSequence text) {
            int i = text.length();

            while (i > 0 && text.charAt(i - 1) == ' ') {
                i--;
            }

            if (i > 0 && text.charAt(i - 1) == ' ') {
                return text;
            } else {
                if (text instanceof Spanned) {
                    SpannableString sp = new SpannableString(text + " ");
                    TextUtils.copySpansFrom((Spanned) text, 0, text.length(), Object.class, sp, 0);
                    return sp;
                } else {
                    return text + " ";
                }
            }
        }

    }
}
